﻿// ===================================
// <copyright>LogoUI Co.</copyright>
// <author>Vlad Spivak</author>
// <email>mailto:vlads@logoui.co.il</email>
// <created>20/00/10</created>
// <lastedit>20/00/10</lastedit>

// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the 'Software'), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
//
//
// <remarks>Part of this software based on various internet sources, mostly on the works
// of members of Wpf Disciples group http://wpfdisciples.wordpress.com/
// Also project may contain code from the frameworks: 
//        Nito 
//        OpenLightGroup
//        nRoute
// </remarks>
// ====================================================================================//


using System;
using System.Windows;
using System.ComponentModel;
using System.Windows.Interactivity;

#if WP7
//todo:check this;
#endif

namespace LogoFX.Infra.Interactivity
{
    /// <summary>
    /// Represents a trigger that can match a value being equal to the given value.
    /// </summary>
    [Obsolete("Use Microsoft.Expression.Interactivity.Core.DataTrigger if possible")]
    public class ValueMatchTrigger
#if WP7
        : BindableTriggerBase<FrameworkElement>
#else
        : TriggerBase<DependencyObject>
#endif
    {
        public static readonly DependencyProperty SourceProperty =
            DependencyProperty.Register("Source", typeof(object), typeof(ValueMatchTrigger), 
            new PropertyMetadata(null, new PropertyChangedCallback(OnSourceChanged)));

        public static readonly DependencyProperty ValueProperty =
            DependencyProperty.Register("Value", typeof(object), typeof(ValueMatchTrigger),
            new PropertyMetadata(null));

        private bool _negate;

#region Properties

        [Category("Common Properties")]
#if (!WP7)
        [CustomPropertyValueEditor(CustomPropertyValueEditor.PropertyBinding)]
#endif
        public object Source
        {
            get { return GetValue(SourceProperty); }
            set { SetValue(SourceProperty, value); }
        }

        [Category("Common Properties")]
#if WP7
        [TypeConverter(typeof(nRoute.Components.TypeConverters.ConvertFromStringConverter))]
#endif
#if (!WP7)
        [CustomPropertyValueEditor(CustomPropertyValueEditor.PropertyBinding)]
#endif
        public Object Value
        {
            get { return GetValue(ValueProperty); }
            set { SetValue(ValueProperty, value); }
        }

        [Category("Common Properties")]
        public bool Negate
        {
            get { return _negate; }
            set { _negate = value; }
        }

#if WP7

        [Category("Common Properties")]
#if (!WP7)
        [CustomPropertyValueEditor(CustomPropertyValueEditor.PropertyBinding)]
#endif
        public Binding SourceBinding
        {
            get { return GetBinding(SourceProperty); }
            set { SetBinding<object>(SourceProperty, value); }
        }

        [Category("Common Properties")]
#if (!WP7)
        [CustomPropertyValueEditor(CustomPropertyValueEditor.PropertyBinding)]
#endif
        public Binding ValueBinding
        {
            get { return GetBinding(ValueProperty); }
            set { SetBinding<object>(ValueProperty, value); }
        }

#endif

#endregion

#region Handlers

        private static void OnSourceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            ((ValueMatchTrigger)d).CompareValue(e.NewValue);
        }

        private void CompareValue(object sourceValue)
        {
            if (this.AssociatedObject == null) return;      // this is to ensure with initial/static set properties the trigger isn't invoked

            // we need to convert it so that the matching can be done
            var _matchValue = sourceValue != null ? ConverterHelper.ConvertToType(Value, sourceValue.GetType()) : null;
            var _result = object.Equals(_matchValue, sourceValue);
            if (Negate) _result = !_result;
            if (_result) base.InvokeActions(sourceValue);
        }

#endregion

    }
}
